package com.jxm.hutools;

import cn.hutool.cache.Cache;
import cn.hutool.cache.CacheUtil;
import cn.hutool.core.date.DateUnit;
import org.junit.Test;

/**
 * @Author: jxm
 * @Description:
 * @Date: 2023-12-19 10:10
 * @Version: 1.0
 */
public class CacheUtilTest {

    //最少使用-LFUCache
    /**
     * LFU(least frequently used) 最少使用率策略。根据使用次数来判定对象是否被持续缓存（使用率是通过访问次数计算），
     * 当缓存满时清理过期对象，清理后依旧满的情况下清除最少访问（访问计数最小）的对象并将其他对象的访问数减去这个最小访问数，
     * 以便新对象进入后可以公平计数。
     */
    @Test
    public void test1(){
        Cache<String, String> lfuCache = CacheUtil.newLFUCache(3);
        //通过实例化对象创建
        //LFUCache<String, String> lfuCache = new LFUCache<String, String>(3);

        lfuCache.put("key1", "value1", DateUnit.SECOND.getMillis() * 3);
        lfuCache.get("key1");//使用次数+1
        lfuCache.put("key2", "value2", DateUnit.SECOND.getMillis() * 3);
        lfuCache.put("key3", "value3", DateUnit.SECOND.getMillis() * 3);
        lfuCache.put("key4", "value4", DateUnit.SECOND.getMillis() * 3);

        //由于缓存容量只有3，当加入第四个元素的时候，根据LRU规则，最少使用的将被移除（2,3被移除）
        String value2 = lfuCache.get("key2");//null
        String value3 = lfuCache.get("key3");//null
        System.out.println(value2);
        System.out.println(value3);
    }

    //最近最久未使用-LRUCache
    /**
     * LRU (least recently used)最近最久未使用缓存。根据使用时间来判定对象是否被持续缓存，当对象被访问时放入缓存，当缓存满了，最久未被使用的对象将被移除。
     * 此缓存基于LinkedHashMap，因此当被缓存的对象每被访问一次，这个对象的key就到链表头部。这个算法简单并且非常快，
     * 他比FIFO有一个显著优势是经常使用的对象不太可能被移除缓存。缺点是当缓存满时，不能被很快的访问。
     */
    @Test
    public void test2(){
        Cache<String, String> lruCache1 = CacheUtil.newLRUCache(3);

        lruCache1.put("key1", "value1", DateUnit.SECOND.getMillis() * 3);
        lruCache1.get("key1");//使用次数+1
        lruCache1.put("key2", "value2", DateUnit.SECOND.getMillis() * 3);
        lruCache1.put("key3", "value3", DateUnit.SECOND.getMillis() * 3);
        lruCache1.put("key4", "value4", DateUnit.SECOND.getMillis() * 3);

        String value1 = lruCache1.get("key1");//null
        System.out.println(value1);

        Cache<String, String> lruCache = CacheUtil.newLRUCache(3);
        //通过实例化对象创建
        //LRUCache<String, String> lruCache = new LRUCache<String, String>(3);
        lruCache.put("key1", "value1", DateUnit.SECOND.getMillis() * 3);
        lruCache.put("key2", "value2", DateUnit.SECOND.getMillis() * 3);
        lruCache.put("key3", "value3", DateUnit.SECOND.getMillis() * 3);
        lruCache.get("key1");//使用时间推近
        lruCache.put("key4", "value4", DateUnit.SECOND.getMillis() * 3);

        //由于缓存容量只有3，当加入第四个元素的时候，根据LRU规则，最少使用的将被移除（2被移除）
        String value2 = lruCache.get("key");//null
    }
}
